#include"Snake.h"
//设置坐标
void setpos(int x,int y)
{
	HANDLE handleput = GetStdHandle(STD_OUTPUT_HANDLE);
	COORD pos = { x , y };
	SetConsoleCursorPosition(handleput, pos);
}

//设置窗口
void ConsoleInit()
{
	system("mode con cols=100 lines=30");
	system("title 贪吃蛇");
	HANDLE handleput = GetStdHandle(STD_OUTPUT_HANDLE);
	CONSOLE_CURSOR_INFO consolecursorinfo;
	GetConsoleCursorInfo(handleput, &consolecursorinfo);
	consolecursorinfo.bVisible = false;
	SetConsoleCursorInfo(handleput, &consolecursorinfo);
}

//展示最初提示
void ShowInitialScreen()
{
	setpos(40, 15);
	printf("欢迎来到贪吃蛇游戏");
	setpos(40, 24);
	system("pause");
	system("cls");
	setpos(25, 15);
	printf("使用↑ ↓ ← → 操控蛇，去吃食物（★、▲、▼），并避免撞到墙（□）");
	setpos(40, 24);
	system("pause");
	system("cls");
	setpos(0, 0);
	for (int i = 0; i < (cols/2); i++)
	{
		printf("□");
	}
	setpos(0, 20);
	for (int i = 0; i < (cols/2); i++)
	{
		printf("□");
	}
	for (int i = 1; i <= lines-1; i++)
	{
		setpos(0, i);
		printf("□");
	}
	for (int i = 1; i <= lines-1; i++)
	{
		setpos(58, i);
		printf("□");
	}

	setpos(65, 8);
	printf("F1加速          F2减速");
	setpos(70, 12);
	printf("当前分数:");
	setpos(70, 13);
	printf("当前速度:");
	setpos(65, 15);
	printf("★5分   ▲7分   ▼10分");
	setpos(65, 16);
	printf("每一点速度都会为食物加2分");
	
}

//创建最开始的蛇
void CreatInitialSnake(Game* game)
{
	Snake* ret = NULL;
	for (int i = 0; i < 5; i++)
	{
		Snake* snake = (Snake*)malloc(sizeof(Snake));
		if (snake != NULL)
		{
			if (i == 4)
			{
				snake->body = L'◆';
			}
			else
			{
				snake->body = L'●';
			}
			snake->x = 30 + i*2;
			snake->y = 9;
			snake->next = ret;
			ret = snake;
			game->snake = snake;
		}
		else
		{
			perror("malloc");
		}
	}
}

//游戏初始化
void GameInit(Game* const game)
{
	game->state = OK;
	game->key = right;
	game->food = uneat;
	game->score = 0;
	game->speed = 0;
	game->extrascore = 0;
}

//创建蛇
Snake* CreateSnake()
{
	Snake* ret = (Snake*)malloc(sizeof(Snake));
	if (ret != NULL)
	{
		ret->body = L'◆';
		ret->next = NULL;
		return ret;
	}
	else
	{
		perror("malloc");
		return NULL;
	}
}

//判断当前状态
void JudgeState(Game* const game)
{
	if (game->snake->x == 0 || game->snake->x == cols - 2 || game->snake->y == 0 || game->snake->y == lines)
	{
		game->state = END_WALL;
		setpos(20, 10);
		printf("你撞到障碍物失败");
		return;
	}
	Snake* ret = game->snake->next;
	while (ret != NULL)
	{
		if (ret->x == game->snake->x && ret->y == game->snake->y)
		{
			game->state = END_BODY;
			setpos(20, 10);
			printf("你撞到自己失败");
			return;
		}
		ret = ret->next;
	}
	if (game->state == END_ESC)
	{
		setpos(20, 10);
		printf("已退出");
	}
	if (game->state==SPACE)
	{
		setpos(0,24);
		system("pause");
		setpos(0, 24);
		printf("                   ");
		game->state = OK;
	}
}


//判断食物是否被吃
void JudgeFoodEated(Game* const game)
{
	if (game->snake->x == game->foodpos.x && game->snake->y == game->foodpos.y)
	{
		if (game->food == score1)
		{
			game->score += (5+game->extrascore);
		}
		else if (game->food == score2)
		{
			game->score += (7 + game->extrascore);
		}
		else if (game->food == score3)
		{
			game->score += (10 + game->extrascore);
		}
		game->food = eated;
	}

}

//生成食物
void Food(Game* const game)
{
	if (game->food == uneat)
	{
		int cl, lin;
	again:
		cl = rand() % (cols-5) + 1;
		lin = rand() % (lines - 2) + 1;
		if ((cl % 2) != 0)
		{
			cl = cl + 1;
		}
		for (Snake* ret = game->snake; ret != NULL; ret = ret->next)
		{
			if (cl == ret->x && lin == ret->y)
			{
				goto again;
			}

		}
		game->foodpos.x = cl;
		game->foodpos.y = lin;
		int score = rand() % 2 + 1;
		if (score == 1)
		{
			game->food = score1;
			setpos(cl, lin);
			printf("★");
		}
		else if (score == 2)
		{
			game->food = score2;
			setpos(cl, lin);
			printf("▲");
		}
		else if (score == 3)
		{
			game->food = score3;
			setpos(cl, lin);
			printf("▼");
		}

	}
	else
	{
		JudgeFoodEated(game);
	}
	
}

void SetGame(Game* game)
{
	CreatInitialSnake(game);
	for (Snake* ret = game->snake; ret != NULL; ret = ret->next)
	{

		setpos(ret->x, ret->y);
		wprintf(L"%lc", ret->body);

	}
	int time = 100;
	do
	{
		//控制按钮
		if (ASYNC(VK_UP) && game->key != down)
		{
			game->key = up;
		}
		else if (ASYNC(VK_DOWN) && game->key != up)
		{
			game->key = down;
		}
		else if (ASYNC(VK_RIGHT) && game->key != left)
		{
			game->key = right;
		}
		else if (ASYNC(VK_LEFT) && game->key != right)
		{
			game->key = left;
		}
		else if (ASYNC(VK_SPACE))
		{
			game->state = SPACE;
		}
		else if (ASYNC(VK_ESCAPE))
		{
			game->state = END_ESC;
		}
		else if (ASYNC(0x70))
		{
			time = time - 20;
			game->extrascore += 2;
			game->speed += 1;

		}
		else if (ASYNC(0x71))
		{
			time = time + 20;
			game->extrascore -= 2;
			game->speed -= 1;
		}
		Snake* con = CreateSnake();
		if (con != NULL)
		{
			if (game->key == up)
			{
				con->body = L'◆';
				con->x = game->snake->x;
				con->y = game->snake->y - 1;
				game->snake->body = L'●';
				con->next = game->snake;
				game->snake = con;
			}
			if (game->key == down)
			{
				con->body = L'◆';
				con->x = game->snake->x;
				con->y = game->snake->y + 1;
				game->snake->body = L'●';
				con->next = game->snake;
				game->snake = con;
			}
			if (game->key == right)
			{
				con->body = L'◆';
				con->x = game->snake->x + 2;
				con->y = game->snake->y;
				game->snake->body = L'●';
				con->next = game->snake;
				game->snake = con;
			}
			if (game->key == left)
			{
				con->body = L'◆';
				con->x = game->snake->x - 2;
				con->y = game->snake->y;
				game->snake->body = L'●';
				con->next = game->snake;
				game->snake = con;
			}

		}
		else
		{
			perror("malloc");
		}
		JudgeState(game);





		//打印游戏进行的画面
		if (game->food != eated)
		{

			for (Snake* ret = game->snake; ret->next != NULL; ret = ret->next)
			{
				if (ret->next->next == NULL)
				{
					setpos(ret->next->x, ret->next->y);
					wprintf(L"%lc", L'　');
					free(ret->next);
					ret->next = NULL;
					break;
				}
			}


		}
		else
		{
			game->food = uneat;
		}
		if (game->snake != NULL && game->snake->next != NULL)
		{
			setpos(game->snake->x, game->snake->y);
			wprintf(L"%lc", game->snake->body);
			setpos(game->snake->next->x, game->snake->next->y);
			wprintf(L"%lc", game->snake->next->body);
			Sleep(time);
		}
		else
		{
			perror("NULL");
		}
		setpos(79, 12);
		printf("%d", game->score);
		setpos(79, 13);
		printf("%d", game->speed);


		Food(game);

	} while (game->state == OK);
}